#!/usr/bin/python3
# -*- coding: utf-8 -*-
# @Time : 2021/10/27 下午2:20
# @Author : The Kite Runner
# @File : dict_server.py
# @Software: PyCharm
from socket import *
from multiprocessing import Process
from dict_db import *


# 进程类
# 处理客户端
class Handle(Process):
    def __init__(self, conn):
        """
        初始化用户名,保存登录的用户名
        @param conn:收发消息套接字
        """
        self.conn = conn
        self.db = Dict()
        self.user = None
        super().__init__()

    # 子进程入口含糊
    def run(self):
        # 循环接收请求分情况讨论
        while True:
            request = self.conn.recv(1024)
            msg = request.decode().split("\t")
            if msg[0] == "R":
                self.do_register(msg[1], msg[2])
            elif msg[0] == "L":
                self.do_login(msg[1], msg[2])
            elif msg[0] == "Q":
                self.do_query(msg[1])
            elif msg[0] == "H":
                self.do_hist()
            elif not request or msg[0] == b"E":
                break
        self.conn.close()
        self.db.close()  # 关闭数据库

    #   注册
    def do_register(self, name, passwd):
        """
        调用数据库函数查看是否可以添加改用户,返回T/F给客户端
        @param name:用户名
        @param passwd: 密码
        @return:
        """
        if self.db.do_register(name, passwd):
            self.conn.send(b"T")
        else:
            self.conn.send(b"F")

    #   登录
    def do_login(self, user, passwd):
        """
        调用数据库登录函数,进行比对该用户是否存在
        @param user:用户名
        @param passwd: 秘密
        @return: 发送T/F给客户端响应
        """
        if self.db.login(user, passwd):
            self.conn.send(b"T")
            self.user = user
        else:
            self.conn.send(b"F")

    #   查询单词
    def do_query(self, word):
        """
        调用数据库函数,得到返回查询单词的结果
        @param word:要查询的单词
        @return: 给客户端发送相应的解释
        """
        data = self.db.query(word)
        if data:
            self.conn.send(data.encode())
            self.db.do_history(self.user, word)
        else:
            self.conn.send(b"F")

    # 查询历史纪录
    def do_hist(self):
        """
        调用数据库函数,查看历史查询纪录,
        得到数据库的返回的所有历史纪录
        循环历史纪录,添加每一条纪录的消息边界
        @return: 返回T历史纪录/F
        """
        # data -->((user,word,time),()) ()
        data = self.db.hist(self.user)
        if data:
            response = "T\t"
            for row in data:
                response += "%s,%s,%s;" % row
            self.conn.send(response.encode())
        else:
            self.conn.send(b"F")


class DictServer:
    def __init__(self):
        self.host = '0.0.0.0'
        self.port = 5555
        self.sock = self.create_sock()

    def create_sock(self):
        """绑定tcp套接字"""
        sock = socket()
        sock.bind((self.host, self.port))
        return sock

    def main(self):
        """入口函数,监听,连接客户端创建子进程"""
        self.sock.listen(5)
        while True:
            conn, addr = self.sock.accept()
            handle = Handle(conn)  # 自定义进程类
            handle.start()


if __name__ == '__main__':
    ftp_server = DictServer()
    ftp_server.main()
